import {
  assignNavigationTask,
  deleteNowRoadnet,
  getOptimalPath,
  mergeRoadnetPath,
  openNowRoadnet,
  synchronousData,
  updateRoadnet
} from '@/api/roadnet'
import { deleteTemplate, getTemplatePathList } from '@/api/template'
import { clearStatus } from '@/shared/map'
import { useCarStore } from '@/stores/car'
import { ElMessage } from '@/stores/elMessage'
import type { TemplateData } from '@/types'
import { i18n } from '@/utils'
import { ConnectorLine, Marker, VectorLayer } from 'maptalks'
import { defineStore } from 'pinia'
import { ref } from 'vue'
import { clearMenu, jumpToCoordinate, map } from './base'
import { clearDrawTool, drawTool } from './drawTool'
import { clearDrawingHomePath, entryPoint, homePathDrawLayer, setEntryPoint } from './home'
import { clearPathLayer } from './path'
import { clearPathToolbarEvent } from './patrolPath'
import { useRecordStore } from './record'
export const useRoadnet = defineStore('roadnet', () => {
  let roadnetPathLayer: VectorLayer

  let connectionPathLayer: VectorLayer

  let navigationPathLayer: VectorLayer

  const roadnetPathDialogVisible = ref<boolean>(false)
  const setRoadnetPathDialogVisible = (value: boolean) => {
    roadnetPathDialogVisible.value = value
  }
  //选择路线
  const roadnetPathToolbarEvent = () => {
    const record = useRecordStore()
    if (record.endRecording()) {
      clearPathToolbarEvent()
      clearDrawTool()
      roadnetPathDialogVisible.value = true
    }
  }

  //绘制起终点
  const optimalPathPoints: any = ref([])
  const drawOptimalPathEvent = () => {
    const record = useRecordStore()
    if (record.endRecording()) {
      clearRoadnetPathLayer()
      clearDrawTool()
      clearMenu()
      setEntryPoint(null)

      drawTool.setMode('Point')
      drawTool.setSymbol({
        markerType: 'ellipse',
        markerFill: 'yellow'
      })
      drawTool.enable()
      drawTool.on('drawend', optimalPathEvent)
    }
  }

  const optimalPathEvent = (e: { geometry: Marker }) => {
    // 鼠标点击的每一个点
    const pathPoint = e.geometry
    pathPoint.setSymbol({
      markerType: 'ellipse',
      markerFill: 'yellow',
      markerWidth: 15,
      markerHeight: 15
    })
    navigationPathLayer.addGeometry(pathPoint)
    if (entryPoint) {
      pathPoint.setCoordinates(entryPoint.getCenter())
      setEntryPoint(null)
    }
    // 点击的点是否存在于路网上
    const exists = pointArray.some((item: any) => {
      return (
        item.getCoordinates().y === pathPoint.getCoordinates().y &&
        item.getCoordinates().x === pathPoint.getCoordinates().x
      )
    })

    if (exists) {
      if (optimalPathPoints.value.length < 2) {
        optimalPathPoints.value.push(pathPoint)
        handleOptimalPathPoints()
      }
    } else {
      navigationPathLayer.removeGeometry(pathPoint)
      ElMessage({
        type: 'error',
        message: i18n.global.t('qing-zai-lu-wang-shang-xuan-ze-qi-dian-zhong-dian')
      })
    }
  }

  // 绘制起点终点后设置菜单
  const handleOptimalPathPoints = () => {
    if (optimalPathPoints.value.length === 2) {
      clearMenu()
      clearDrawTool()
      setDrawEndMenu(saveOptimalPathPointMenu)
    }
  }

  // 获取路网的导航路线点数据集合
  const navigationData: any = ref([])

  // 点集合
  const navigationArray: Marker[] = []

  const saveOptimalPathPointMenu = [
    {
      item: i18n.global.t('que-ding'),
      click: async () => {
        clearMenu()
        navigationPathLayer.clear()
        pointArray.forEach((item: Marker) => {
          item.setSymbol({
            markerType: 'ellipse',
            markerFill: '#FF0070',
            markerWidth: 15,
            markerHeight: 15
          })
        })
        fetchAndDisplayOptimalPath()
      }
    },
    {
      item: i18n.global.t('qu-xiao'),
      click: cancelDrawConnectionEvent
    }
  ]

  async function fetchAndDisplayOptimalPath() {
    try {
      //获取导航路线 下发
      const carStore = useCarStore()
      const res: any = await getOptimalPath({
        destinationPoint: {
          x: optimalPathPoints.value[0].getCoordinates().y,
          y: optimalPathPoints.value[0].getCoordinates().x
        },
        robotCode: carStore.currentCar,
        sourcePoint: {
          x: optimalPathPoints.value[1].getCoordinates().y,
          y: optimalPathPoints.value[1].getCoordinates().x
        }
      })

      navigationData.value = res.data
      ElMessage({ type: 'success', message: res.message })
      displayPath(navigationData.value)
    } catch (error) {
      optimalPathPoints.value.length = 0
      navigationData.value.length = 0
      navigationArray.length = 0
      nowRoadnetEvent()
    }
  }

  function displayPath(data: { x: number; y: number }[]) {
    data.forEach((item, index) => {
      const navigationPointMarker = new Marker([item.y, item.x], {
        symbol: {
          markerType: 'ellipse',
          markerFill: 'yellow',
          markerWidth: 15,
          markerHeight: 15
        },
        draggable: false
      })
      navigationArray.push(navigationPointMarker)

      navigationPathLayer.addGeometry(navigationPointMarker)

      if (index > 0) {
        const lastPoint = navigationArray[index - 1]
        const connectLine = new ConnectorLine(lastPoint, navigationPointMarker, {
          showOn: 'always',
          symbol: { lineColor: 'yellow' },
          zIndex: -1
        })
        navigationPathLayer.addGeometry(connectLine)
      }
    })

    setDrawEndMenu([
      {
        item: i18n.global.t('qu-xiao'),
        click: cancelDrawConnectionEvent
      }
    ])
  }

  // 路网导航下发
  const assignNavigationTaskEvent = async () => {
    if (navigationData.value.length > 1) {
      const carStore = useCarStore()
      const res: any = await assignNavigationTask(carStore.currentCar, navigationData.value)
      ElMessage({
        type: 'success',
        message: res.message
      })
      clearRoadnetLayer()
      clearMenu()
      setDrawEndMenu([
        {
          item: i18n.global.t('qing-kong'),
          click: () => {
            clearMenu()
            clearRoadnetPathLayer()
          }
        }
      ])
    } else {
      ElMessage({
        type: 'error',
        message: i18n.global.t('wei-huo-qu-dao-hang-lu-xian')
      })
    }
  }

  // 同步数据
  const synchronousDataEvent = async () => {
    const res: any = await synchronousData()
    ElMessage({
      type: 'success',
      message: res.message
    })
  }

  // 点实例集合
  const pointArray: Marker[] = []
  let dragendPoint: any
  let pointMarker: any
  // 当前路网
  const nowRoadnetEvent = async () => {
    if (homePathDrawLayer) {
      clearDrawingHomePath()
    }
    clearPathToolbarEvent()
    const record = useRecordStore()
    if (record.endRecording()) {
      clearMenu()
      clearRoadnetLayer()
      clearDrawTool()
      clearPathLayer()
      const res: any = await openNowRoadnet('1')

      setPointList(res)
      setConnectList(res)
      if (res.data.pointList.length > 0) {
        jumpToCoordinate(res.data.pointList[0].y, res.data.pointList[0].x, map)
      } else {
        ElMessage({
          type: 'error',
          message: i18n.global.t('dang-qian-wu-lu-wang-shu-ju')
        })
      }
    }
    setDrawEndMenu(connectionPathMenu)
  }

  function setPointList(res: any) {
    //  点数据集合
    const pointList = JSON.parse(JSON.stringify(res.data.pointList))

    pointList.map((item: any, index: number) => {
      pointMarker = new Marker([item.y, item.x], {
        symbol: {
          markerType: 'ellipse',
          markerFill: '#FF0070',
          markerWidth: 15,
          markerHeight: 15
        },
        draggable: false
      })
        .on('click', (e: { target: Marker }) => {
          setEntryPoint(e.target)
        })
        .on('mousedown', (e: { target: Marker }) => {
          // 拖动前的值
          dragendPoint = {
            x: e.target.getCoordinates().y,
            y: e.target.getCoordinates().x
          }
        })
        .on('dragend', function (e) {
          // 拖拽完更新点实例集合
          pointArray[index] = e.target
          connectionPathsData.value.forEach((i: any, index: number) => {
            if (dragendPoint.x === i.firstPoint.x && dragendPoint.y === i.firstPoint.y) {
              connectionPathsData.value[index].firstPoint.x = e.target.getCoordinates().y
              connectionPathsData.value[index].firstPoint.y = e.target.getCoordinates().x
            }
            if (dragendPoint.x === i.secondPoint.x && dragendPoint.y === i.secondPoint.y) {
              connectionPathsData.value[index].secondPoint.x = e.target.getCoordinates().y
              connectionPathsData.value[index].secondPoint.y = e.target.getCoordinates().x
            }
          })
        })
      // 显示路网时的所有点实例
      pointArray.push(pointMarker)

      roadnetPathLayer.addGeometry(pointMarker)
    })
  }

  function setConnectList(res: any) {
    const connectList = JSON.parse(JSON.stringify(res.data.connectList))

    connectList.forEach((i: any) => {
      connectionPathsData.value.push(i)
      const lastTwoPoints: any = []
      // 连接点
      pointArray.forEach((item: any) => {
        if (
          (item.getCoordinates().y === i.firstPoint.x &&
            item.getCoordinates().x === i.firstPoint.y) ||
          (item.getCoordinates().y === i.secondPoint.x &&
            item.getCoordinates().x === i.secondPoint.y)
        ) {
          lastTwoPoints.push(item)
          const connectLine = new ConnectorLine(lastTwoPoints[0], lastTwoPoints[1], {
            showOn: 'always',
            symbol: {
              lineColor: 'pink'
            },
            zIndex: -1
          })
          roadnetPathLayer.addGeometry(connectLine)
        }
      })
    })
  }

  const roadnetPathSaveEvent = async () => {
    const record = useRecordStore()
    if (record.endRecording()) {
      clearDrawTool()

      // 连接线集合
      if (connectionPathsArray.value.length > 0) {
        connectionPathsArray.value.map((item: any) => {
          connectionPathsData.value.push(item)
        })
      }

      await saveRoadnetPath(connectionPathsData.value, pointArray)
      connectLineArray.value.length = 0
      clearRoadnetLayer()
      clearRoadnetPathLayer()
      clearMenu()
    }
  }

  const saveRoadnetPath = async (connectListValue: any, pointListValue: any) => {
    if (pointListValue.length !== 0 && connectListValue.length !== 0) {
      pointListValue = pointListValue.map((item: any) => {
        return { x: item.getCoordinates().y, y: item.getCoordinates().x }
      })

      // 保存路网
      const res: any = await updateRoadnet({
        connectList: connectListValue,
        pointList: pointListValue
      })
      ElMessage({
        type: 'success',
        message: res.message
      })
    } else {
      ElMessage({
        type: 'error',
        message: i18n.global.t('wei-xuan-ze-lu-xian')
      })
    }
  }

  /**
   * 初始化路线图层
   */
  const initRoadnetPathLayer = () => {
    roadnetPathLayer = new VectorLayer('roadnet-line')
    roadnetPathLayer.addTo(map)
  }

  const initConnectionPathLayer = () => {
    connectionPathLayer = new VectorLayer('connection-line')
    connectionPathLayer.addTo(map)
  }

  const initNavigationPathLayer = () => {
    navigationPathLayer = new VectorLayer('navigation-line')
    navigationPathLayer.addTo(map)
  }

  /**
   * 清空路网图层
   */
  const clearRoadnetLayer = () => {
    roadnetPathLayer.clear()
    connectionPathLayer.clear()
    connectionPathsData.value.length = 0
    pointArray.length = 0
    connectionPathsArray.value.length = 0
  }

  /**
   * 清空导航路线图层
   */
  const clearRoadnetPathLayer = () => {
    navigationPathLayer.clear()
    optimalPathPoints.value.length = 0
    navigationData.value.length = 0
    navigationArray.length = 0
  }

  const connectionPathsData: any = ref([])

  const setDrawEndMenu = (roadnetPathMenu: any) => {
    map.setMenuItems(roadnetPathMenu)
  }

  const drawConnectionPathEvent = () => {
    const record = useRecordStore()
    if (record.endRecording()) {
      clearMenu()
      clearDrawTool()
      setEntryPoint(null)
      setDrawEndMenu(cancelDrawConnectionMenu)
      drawTool.setMode('Point')
      drawTool.setSymbol({
        markerType: 'ellipse',
        markerFill: '#FF0070'
      })
      drawTool.enable()
      drawTool.on('drawend', connectionPathDrawendEvent)
    }
  }

  const lastTwoPoints: any = []
  const connectLineArray = ref<ConnectorLine[]>([])
  const connectionPathsArray: any = ref([])
  const connectionPathDrawendEvent = (e: { geometry: Marker }) => {
    // 连接模式鼠标点击的每一个点
    const pathPoint = e.geometry
    if (entryPoint) {
      pathPoint.setCoordinates(entryPoint.getCenter())
      setEntryPoint(null)
    }

    // 点击的点是否存在于路网上
    const exists = pointArray.some((item: any) => {
      return (
        item.getCoordinates().y === pathPoint.getCoordinates().y &&
        item.getCoordinates().x === pathPoint.getCoordinates().x
      )
    })

    if (exists) {
      lastTwoPoints.push(pathPoint)
      if (lastTwoPoints.length === 2) {
        const connectLine = new ConnectorLine(lastTwoPoints[0], lastTwoPoints[1], {
          showOn: 'always',
          symbol: {
            lineColor: '#ff930e'
          },
          zIndex: -1
        })

        connectionPathLayer.addGeometry(connectLine)
        const getConnectionPathPoints = lastTwoPoints.map((item: any) => {
          return {
            x: item.getCoordinates().y,
            y: item.getCoordinates().x
          }
        })
        connectionPathsArray.value.push({
          firstPoint: getConnectionPathPoints[0],
          secondPoint: getConnectionPathPoints[1]
        })

        connectLineArray.value.push(connectLine)
        lastTwoPoints.length = 0
        setConnectLineMenu()
      }
      if (connectLineArray.value.length > 0) {
        setConnectLineMenu()
      }
    } else {
      ElMessage({
        type: 'error',
        message: i18n.global.t('qing-zai-lu-xian-dian-shang-jin-hang-lian-jie')
      })
    }
  }

  //添加线的菜单
  const setConnectLineMenu = () => {
    connectLineArray.value.forEach((connectLine: ConnectorLine, index: number) => {
      connectLine.removeMenu()
      const connectLineMenuItems = [
        {
          item: i18n.global.t('shan-chu'),
          click: () => {
            deleteConnectLine(connectLine, index)
          }
        }
      ]
      connectLine.setMenuItems(connectLineMenuItems)
    })
  }

  // 删除线
  const deleteConnectLine = (item: ConnectorLine, i: number) => {
    item.hide()
    connectLineArray.value.splice(i, 1)
    connectionPathsArray.value.splice(i, 1)
    setConnectLineMenu()
  }

  const cancelDraggableMenu = [
    {
      item: i18n.global.t('qu-xiao'),
      click: () => {
        ElMessage({ type: 'info', message: i18n.global.t('qu-xiao-tuo-dong') })
        nowRoadnetEvent()
      }
    },
    {
      item: i18n.global.t('lian-jie'),
      click: connectionPointEvent
    },
    {
      item: i18n.global.t('bao-cun-lu-wang'),
      click: roadnetPathSaveEvent
    }
  ]

  const connectionPathMenu = [
    {
      item: i18n.global.t('lian-jie'),
      click: connectionPointEvent
    },
    {
      item: i18n.global.t('tuo-dong'),
      click: draggablePointEvent
    },
    {
      item: i18n.global.t('dao-hang-hui-zhi'),
      click: drawOptimalPathEvent
    },
    /**
     * 清除路网数据
     */
    {
      item: i18n.global.t('qing-chu-lu-wang'),
      click: clearRoadnetEvent
    }
  ]

  function connectionPointEvent() {
    drawConnectionPathEvent()
    // 点击连接菜单时不能拖动点
    pointArray.forEach((item: any) => {
      item.config('draggable', false)
    })
  }

  async function draggablePointEvent() {
    // 点击拖动菜单时可以拖动点
    pointArray.forEach((item: any) => {
      item.config('draggable', true)
    })
    setDrawEndMenu(cancelDraggableMenu)
  }

  async function clearRoadnetEvent() {
    const res: any = await deleteNowRoadnet('1')
    ElMessage({
      type: 'success',
      message: res.message
    })
    clearRoadnetLayer()
    clearRoadnetPathLayer()
    clearMenu()
  }

  const cancelDrawConnectionMenu = [
    {
      item: i18n.global.t('qu-xiao'),
      click: cancelDrawConnectionEvent
    },
    {
      item: i18n.global.t('bao-cun-lu-wang'),
      click: roadnetPathSaveEvent
    }
  ]

  //取消
  function cancelDrawConnectionEvent() {
    clearMenu()
    // 取消绘制路线
    if (optimalPathPoints.value.length > 0) {
      ElMessage({
        type: 'info',
        message: i18n.global.t('qu-xiao-dao-hang-hui-zhi')
      })
      clearRoadnetPathLayer()
    } else {
      // 取消连接功能
      ElMessage({
        type: 'info',
        message: i18n.global.t('qu-xiao-lian-jie')
      })
      connectionPathLayer.clear()
      connectionPathsArray.value.length = 0
      clearDrawTool()
    }
    setDrawEndMenu(connectionPathMenu)
  }

  const initialParams = {
    limit: 10,
    page: 1,
    rtype: 'patroling',
    type: 2
  }

  const params: Record<string, any> = ref(Object.assign({}, initialParams))

  const list = ref<any[]>([])
  const total = ref(0)

  // 获取列表数据
  async function getList() {
    const res = await getTemplatePathList(params.value)
    list.value = res.data.list || []
    total.value = res.data ? res.data.total : 0
  }

  async function handleQuery() {
    await getList()
  }

  function setParams(val: { name: string; memo: string }) {
    params.value = val
  }
  async function handleReset() {
    params.value = Object.assign({}, initialParams)
    await getList()
  }

  const currentTemplate = ref<any[]>([])
  function onCurrentChange(val: any[]) {
    currentTemplate.value = val
  }

  // 路网路线集合
  const roadnetPaths: any = ref([])
  const missionTemplateIds: any = ref([])
  const onComfirm = async () => {
    if (currentTemplate.value) {
      roadnetPaths.value.length = 0
      missionTemplateIds.value.length = 0
      clearStatus()
      clearMenu()
      clearRoadnetLayer()
      clearRoadnetPathLayer()
      //选择路线
      roadnetPaths.value = currentTemplate.value.map((i: TemplateData) => {
        missionTemplateIds.value.push(i.id)
        return JSON.parse(i!.mission)
      })

      const res: any = await mergeRoadnetPath({
        id: 1,
        routeList: missionTemplateIds.value
      })
      ElMessage({
        type: 'success',
        message: res.message
      })
      setRoadnetPathDialogVisible(false)
      nowRoadnetEvent()
    } else {
      ElMessage({
        type: 'warning',
        message: i18n.global.t('wei-xuan-ze-rong-he-lu-xian')
      })
    }
  }

  function closeDialog() {
    roadnetPathDialogVisible.value = false
  }

  // 删除路网路线
  async function handleDelete(id: number) {
    const res: any = await deleteTemplate(id)
    ElMessage({ type: 'success', message: res.message })
    getList()
  }

  return {
    roadnetPathDialogVisible,
    roadnetPathToolbarEvent,
    nowRoadnetEvent,
    roadnetPathSaveEvent,
    initRoadnetPathLayer,
    initConnectionPathLayer,
    initNavigationPathLayer,
    clearRoadnetLayer,
    setRoadnetPathDialogVisible,
    getList,
    params,
    onCurrentChange,
    list,
    handleReset,
    handleQuery,
    total,
    onComfirm,
    setParams,
    currentTemplate,
    missionTemplateIds,
    roadnetPaths,
    closeDialog,
    assignNavigationTaskEvent,
    synchronousDataEvent,
    handleDelete,
    clearRoadnetPathLayer
  }
})
